﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Web;
using System.Text;
using AidBrella.Entities;
using Aidbrella.Model;
using System.Data;

namespace AidBrella.WCFServiceWebRole
{    
    public class AidBrellaService : IAidBrellaService
    {
        public Project GetProjectById(int id)
        {
            using (var ctx = new AidBrellaModelContainer())
            {
                ctx.ContextOptions.ProxyCreationEnabled = false;
                return ctx.ProjectSet.Where(ps => ps.Id == id).FirstOrDefault();
            }
        }

        public IList<ProjectSite> GetProjectSites(int projectId)
        {
            using (var ctx = new AidBrellaModelContainer())
            {
                ctx.ContextOptions.ProxyCreationEnabled = false;
                return ctx.ProjectSiteSet.Where(ps => ps.ProjectId == projectId).ToList();
            }
        }

        public void AddProjectSite(int projectId, double longitude, double latitude)
        {
            using (var ctx = new AidBrellaModelContainer())
            {
                var projectSite = new ProjectSite()
                {
                    ProjectId = projectId,
                    Longitude = longitude,
                    Latitude = latitude
                };
                ctx.ProjectSiteSet.AddObject(projectSite);
                ctx.SaveChanges();
            }
        }        

        public void DeleteProjectSite(int projectSiteId, int projectId)
        {
            using (var ctx = new AidBrellaModelContainer())
            {
                var projectSite = new ProjectSite()
                {
                    Id = projectSiteId,
                    ProjectId = projectId
                };
                ctx.ProjectSiteSet.DeleteObject(projectSite);
                ctx.SaveChanges();
            }
        }

        public void CreateUser(string userName, string firstName, string lastName, string email)
        {
            using (var ctx = new AidBrellaModelContainer())
            {
                var user = new User
                {
                    UserName = userName,                    
                    FirstName = firstName,
                    LastName = lastName,
                    Email = email,
                    Created = DateTime.Now,
                    Modified = DateTime.Now
                };
                ctx.UserSet.AddObject(user);
                ctx.SaveChanges();
            }
        }


        #region IAidBrellaService Members


        // TODO: business logic based on authenticated user roles


        public List<Organization> GetOrganizations()
        {
            var organizations = new List<Organization>();
            using (var ctx = new AidBrellaModelContainer())
            {
                ctx.ContextOptions.ProxyCreationEnabled = false;
                organizations = ctx.OrganizationSet.ToList();
            }

            return organizations;
        }

        public Entities.Organization GetOrganization(int organizationId)
        {
            var mdl = new Aidbrella.Model.AidBrellaModelContainer();
            mdl.ContextOptions.ProxyCreationEnabled = false;
            return mdl.OrganizationSet.FirstOrDefault(
                o =>  o.Id == organizationId 
                );
        }

        public Entities.User GetUser(int userid)
        {
            var mdl = new Aidbrella.Model.AidBrellaModelContainer();
            mdl.ContextOptions.ProxyCreationEnabled = false;
            return mdl.UserSet.FirstOrDefault(u => u.Id == userid);
        }

        public List<Entities.Project> GetProjectsOfOrganization(int organizationId)
        {
            var mdl = new Aidbrella.Model.AidBrellaModelContainer();
            mdl.ContextOptions.ProxyCreationEnabled = false;
            var pl = mdl.OrganizationProjectSet.Where(p => p.OrganizationId == organizationId);

            return pl.Select(pr => pr.Project).ToList();
        }

        public List<Entities.User> GetUsersOfProject(int projectId)
        {
            var mdl = new Aidbrella.Model.AidBrellaModelContainer();
            mdl.ContextOptions.ProxyCreationEnabled = false;
            var prjs = mdl.ProjectUserSet;
            var projectusers = prjs.Where(pu => pu.ProjectId == projectId);

        	return projectusers.Select(pu => pu.User).ToList();
        }

        public List<Entities.User> GetUsersOfOrganization(int organizationId)
        {
            // TODO: this is potentially very expensive, figure out a replacement if needed
            //var mdl = new Aidbrella.Model.AidBrellaModelContainer();

            //var usersinroles = new List<AidBrella.Entities.OrganizationRoleUser>();

            //foreach (var uir in mdl.OrganizationRoleUserSet.Where(o => o.))
throw new NotImplementedException();
        }

        public List<Entities.User> GetUsersOfProjects(int userId)
        {
            var mdl = new Aidbrella.Model.AidBrellaModelContainer();
            mdl.ContextOptions.ProxyCreationEnabled = false;
            var pu = mdl.ProjectUserSet.Where(u => u.UserId == userId);

        	return pu.Select(p => p.User).ToList();
        }

        public List<Entities.OrganizationRoleUser> GetRolesForUserInOrganization(int userId)
        {
            var mdl = new Aidbrella.Model.AidBrellaModelContainer();
            mdl.ContextOptions.ProxyCreationEnabled = false;
            var oru = mdl.OrganizationRoleUserSet.Where(o => o.UserId == userId);
            return oru.ToList();

        }

        public List<Entities.ProjectSite> GetSitesForProject(int projectId)
        {
            var mdl = new Aidbrella.Model.AidBrellaModelContainer();
            mdl.ContextOptions.ProxyCreationEnabled = false;
            var ps = mdl.ProjectSiteSet.Where (p => p.ProjectId == projectId );
            return ps.ToList();

        }

        public List<Entities.ProjectSite> GetSitesForOrganization(int organizationId)
        {
            var mdl = new Aidbrella.Model.AidBrellaModelContainer();
            mdl.ContextOptions.ProxyCreationEnabled = false;
            var ps = mdl.ProjectSiteSet.Where(p => p.Project.OrganizationProject.Any((o)=>o.OrganizationId==organizationId));
            return ps.ToList();
            
        }

        public List<Entities.User> GetUsersForSite(int siteId)
        {
            throw new NotImplementedException();
            //var mdl = new Aidbrella.Model.AidBrellaModelContainer();

            
        }

        public List<Entities.ProjectSite> GetNearbySites(double lat, double lon)
        {
            throw new NotImplementedException();
        }

        public IList<OrganizationType> GetOraganizationTypes()
        {            
            IList<OrganizationType> organizationTypes = new List<OrganizationType>();
            using (var ctx = new AidBrellaModelContainer())
            {
                ctx.ContextOptions.ProxyCreationEnabled = false;
                organizationTypes = ctx.OrganizationType.ToList();
            }

            return organizationTypes;
        }

        #endregion


        List<Project> IAidBrellaService.GetProjectsForUser(int userId)
        {
            List<ProjectResult> projectsResult = null;
            using (var ctx = new AidBrellaModelContainer())
            {
                ctx.ContextOptions.ProxyCreationEnabled = false;
                var userProjects = ctx.ProjectUserSet.Where(p => p.UserId == userId).Select(p=> p.ProjectId).ToList();
                projectsResult = (from p in ctx.ProjectResultSet where userProjects.Contains(p.ProjectId) select p).ToList();

            }

            return projectsResult.Select(pr => pr.Project).ToList();
        }
    }
}
